<template>
    <van-pull-refresh v-model="refreshing" @refresh="onRefresh">
        <van-list v-model:loading="loading" v-model:error="error" :finished="isFinished" :error-text="errorText"
            :immediate-check="false" @load="onLoad">
            <!-- 列表内容插槽 -->
            <template v-if="!error">
                <!-- 首次加载显示加载状态 -->
                <template v-if="firstLoading">
                    <div class="first-loading">
                        <van-loading size="24px" vertical>加载中...</van-loading>
                    </div>
                </template>
                <!-- 有数据时显示列表 -->
                <template v-else-if="list.length > 0">
                    <slot :list="list"></slot>
                </template>
                <!-- 加载完成且无数据时显示空状态 -->
                <template v-else-if="!loading && isFinished">
                    <slot name="empty" :loading="loading" :error="error">
                        <van-empty :description="emptyText" :image="emptyImage">
                        </van-empty>
                    </slot>
                </template>
            </template>

            <!-- 加载更多状态 - 只在非首次加载时显示 -->
            <template #loading>
                <slot name="loading" v-if="!firstLoading">
                    <div class="load-more">
                        <van-loading size="16px">加载更多...</van-loading>
                    </div>
                </slot>
            </template>

            <!-- 完成状态 -->
            <template #finished>
                <slot v-if="showFinishedText && list.length > 0" name="finished">
                    <div class="list-finished">{{ finishedText }}</div>
                </slot>
            </template>

            <!-- 错误状态 -->
            <template #error>
                <slot name="error">
                    <div class="list-error">
                        <van-empty image="error" :description="errorText">
                            <template #default>
                                <van-button round type="primary" class="retry-btn" @click="onRetry">
                                    重试
                                </van-button>
                            </template>
                        </van-empty>
                    </div>
                </slot>
            </template>
        </van-list>
    </van-pull-refresh>
</template>

<script setup>
    import { ref, computed } from 'vue'
    import { showToast } from 'vant'

    const props = defineProps({
        // 请求方法
        request: {
            type: Function,
            required: true
        },
        // 数据处理方法
        transform: {
            type: Function,
            default: data => data
        },
        // 分页大小
        pageSize: {
            type: Number,
            default: 10
        },
        // 是否显示完成文本
        showFinishedText: {
            type: Boolean,
            default: true
        },
        // 完成文本
        finishedText: {
            type: String,
            default: '没有更多了'
        },
        // 空状态文本
        emptyText: {
            type: String,
            default: '暂无数据'
        },
        // 空状态图片
        emptyImage: {
            type: String,
            default: 'empty'
        },
        // 错误文本
        errorText: {
            type: String,
            default: '加载失败，请重试'
        }
    })

    // 内部状态
    const page = ref(1)
    const list = ref([])
    const loading = ref(false)
    const refreshing = ref(false)
    const error = ref(false)
    const totalItems = ref(0)
    const lastPageSize = ref(props.pageSize)
    const firstLoading = ref(true) // 添加首次加载状态

    // 计算是否加载完成
    const isFinished = computed(() => {
        // 如果最后一次请求返回空数组或数据量小于 pageSize，则认为加载完成
        return lastPageSize.value === 0 || lastPageSize.value < props.pageSize
    })

    // 重置状态
    const reset = () => {
        page.value = 1
        list.value = []
        totalItems.value = 0
        error.value = false
        lastPageSize.value = props.pageSize  // 重置最后一页数据条数
    }

    // 加载数据
    const loadData = async () => {
        if (loading.value) return

        try {
            loading.value = true
            error.value = false

            const res = await props.request({
                pageNum: page.value,
                pageSize: props.pageSize
            })

            if (res.code === 0) {
                let pageData = res.data
                let total = res.data.length
                console.log(pageData, "1212pageData", total)
                const transformedData = props.transform(pageData)

                // 记录本次请求返回的数据条数
                lastPageSize.value = pageData.length

                if (page.value === 1) {
                    list.value = transformedData
                } else {
                    list.value = [...list.value, ...transformedData]
                }

                totalItems.value = parseInt(total)
                page.value++

                // 如果是空数组或数据条数小于 pageSize，说明没有更多数据了
                if (pageData.length === 0 || pageData.length < props.pageSize) {
                    loading.value = false
                    // 设置加载完成状态
                    isFinished.value = true
                }

            } else {
                throw new Error(res.msg || '加载失败')
            }
        } catch (err) {
            console.error('Load error:', err)
            error.value = true
            showToast(err.message)
        } finally {
            loading.value = false
            refreshing.value = false
            firstLoading.value = false // 首次加载完成
        }
    }

    // 下拉刷新
    const onRefresh = async () => {
        reset()
        await loadData()
    }

    // 上拉加载
    const onLoad = () => {
        if (!isFinished.value) {  // 只在未完成时触发加载
            loadData()
        }
    }

    // 重试
    const onRetry = () => {
        error.value = false
        loadData()
    }

    // 暴露方法给父组件
    defineExpose({
        reset,
        reload: onRefresh
    })
</script>

<style lang="scss" scoped>
    .van-pull-refresh {
        background: #ffffff;
        min-height: calc(100vh - 32px);
    }

    .van-list {
        height: 100%;

        ::v-deep .van-empty {

            display: flex;
            flex-direction: column;
            align-items: center;
            justify-content: center;
            min-height: 80vh;

            .van-empty__image {
                width: 50px;
                height: 50px;
            }
        }
    }

    .list-finished {
        padding: 16px 0;
        color: #969799;
        font-size: 14px;
        text-align: center;
    }

    .list-error {
        padding: 16px 0;
    }

    .retry-btn {
        margin-top: 16px;
        width: 160px;
    }

    .first-loading {
        display: flex;
        justify-content: center;
        align-items: center;
        min-height: 200px; // 给予足够的高度
        padding: 32px 0;
    }

    .load-more {
        padding: 16px 0;
        text-align: center;
        color: #969799;
        font-size: 14px;
    }
</style>